package info.batcloud.fanli.api.controller;

import info.batcloud.fanli.core.dto.UserDTO;
import info.batcloud.fanli.core.dto.WalletDTO;
import info.batcloud.fanli.core.domain.BusinessResponse;
import info.batcloud.fanli.core.domain.stat.UserCommissionEarning;
import info.batcloud.fanli.core.domain.stat.UserMonthSettleEarning;
import info.batcloud.fanli.core.enums.AgentType;
import info.batcloud.fanli.core.enums.CommissionAllotType;
import info.batcloud.fanli.core.enums.UserLevel;
import info.batcloud.fanli.core.helper.SecurityHelper;
import info.batcloud.fanli.core.mapper.stat.UserCommissionEarningMapper;
import info.batcloud.fanli.core.service.AgentService;
import info.batcloud.fanli.core.service.UserService;
import info.batcloud.fanli.core.service.WalletService;
import org.apache.commons.lang.StringUtils;
import org.apache.commons.lang3.time.DateUtils;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import javax.inject.Inject;
import java.text.ParseException;
import java.util.*;

@RestController
@RequestMapping("/page/earning")
public class PageEarningController {

    @Inject
    private WalletService walletService;

    @Inject
    private UserService userService;

    @Inject
    private UserCommissionEarningMapper userCommissionEarningMapper;

    @Inject
    private AgentService agentService;

    @GetMapping("/data")
    @PreAuthorize("hasRole('USER')")
    public Object data() throws ParseException {
        UserDTO user = userService.findById(SecurityHelper.loginUserId());
        Map<String, Object> model = new HashMap<>();
        Long userId = user.getId();
        WalletDTO wallet = walletService.findByUserId(userId);
        model.put("obtainedMoney", wallet.getObtainedMoney());
        model.put("money", wallet.getMoney());
        Date now = new Date();
        Date yesterdayStartTime = DateUtils.truncate(DateUtils.addDays(now, -1), Calendar.DATE);
        UserCommissionEarningMapper.UserEstimateStatParam dayEstimateStateParam = new UserCommissionEarningMapper.UserEstimateStatParam();
        dayEstimateStateParam.setUserId(SecurityHelper.loginUserId());
        dayEstimateStateParam.setStartTime(yesterdayStartTime);
        dayEstimateStateParam.setEndTime(now);
        dayEstimateStateParam.setTimeDimension(UserCommissionEarningMapper.TimeDimension.DAY);
        this.stat(model, dayEstimateStateParam);
        //两个月的统计
        Date lastMonthStartTime = DateUtils.truncate(DateUtils.addMonths(now, -1), Calendar.MONTH);
        dayEstimateStateParam.setUserId(SecurityHelper.loginUserId());
        dayEstimateStateParam.setStartTime(lastMonthStartTime);
        dayEstimateStateParam.setEndTime(now);
        dayEstimateStateParam.setTimeDimension(UserCommissionEarningMapper.TimeDimension.MONTH);
        this.stat(model, dayEstimateStateParam);
        UserCommissionEarningMapper.UserMonthSettleStatParam settleStatParam = new UserCommissionEarningMapper.UserMonthSettleStatParam();
        settleStatParam.setUserId(SecurityHelper.loginUserId());
        settleStatParam.setStartTime(lastMonthStartTime);
        settleStatParam.setEndTime(now);
        List<UserMonthSettleEarning> userMonthSettleEarnings = userCommissionEarningMapper.userMonthSettleEarning(settleStatParam);
        for (UserMonthSettleEarning monthSettleEarning : userMonthSettleEarnings) {
            String keyPrefix;
            Date date = DateUtils.parseDate(monthSettleEarning.getDate() + "-01", "yyyy-MM-dd");
            if (DateUtils.truncate(date, Calendar.MONTH).equals(DateUtils.truncate(now, Calendar.MONTH))) {
                keyPrefix = "month";
            } else {
                keyPrefix = "lastMonth";
            }
            model.put(keyPrefix + "SettledFee", monthSettleEarning.getSettledFee());
            model.put(keyPrefix + "SettledCommissionFee", monthSettleEarning.getSettledCommissionFee());
            model.put(keyPrefix + "SettledRewardFee", monthSettleEarning.getSettledRewardFee());
            model.put(keyPrefix + "SettledOrderNum", monthSettleEarning.getOrderNum());
            model.put(keyPrefix + "SelfBuySettledOrderNum", monthSettleEarning.getSelfBuyOrderNum());
            model.put(keyPrefix + "DirectSettledOrderNum", monthSettleEarning.getDirectOrderNum());
            model.put(keyPrefix + "IndirectSettledOrderNum", monthSettleEarning.getIndirectOrderNum());
            model.put(keyPrefix + "CarrierSettledOrderNum", monthSettleEarning.getCarrierOrderNum());
            model.put(keyPrefix + "ChiefSettledOrderNum", monthSettleEarning.getChiefOrderNum());
            model.put(keyPrefix + "CityAgentSettledOrderNum", monthSettleEarning.getCityAgentOrderNum());
            model.put(keyPrefix + "DistrictAgentSettledOrderNum", monthSettleEarning.getDistrictAgentOrderNum());
            model.put(keyPrefix + "RelationAgentSettledOrderNum", monthSettleEarning.getRelationAgentOrderNum());
            model.put(keyPrefix + "SelfBuySettledCommissionFee", monthSettleEarning.getSelfBuySettledCommissionFee());
            model.put(keyPrefix + "DirectSettledCommissionFee", monthSettleEarning.getDirectSettledCommissionFee());
            model.put(keyPrefix + "IndirectSettledCommissionFee", monthSettleEarning.getIndirectSettledCommissionFee());
            model.put(keyPrefix + "CarrierSettledCommissionFee", monthSettleEarning.getCarrierSettledCommissionFee());
            model.put(keyPrefix + "ChiefSettledCommissionFee", monthSettleEarning.getChiefSettledCommissionFee());
            model.put(keyPrefix + "CityAgentSettledCommissionFee", monthSettleEarning.getCityAgentSettledCommissionFee());
            model.put(keyPrefix + "DistrictAgentSettledCommissionFee", monthSettleEarning.getDistrictAgentSettledCommissionFee());
            model.put(keyPrefix + "RelationAgentSettledCommissionFee", monthSettleEarning.getRelationAgentSettledCommissionFee());
            model.put(keyPrefix + "SelfBuySettledRewardFee", monthSettleEarning.getSelfBuySettledRewardFee());
            model.put(keyPrefix + "DirectSettledRewardFee", monthSettleEarning.getDirectSettledRewardFee());
            model.put(keyPrefix + "IndirectSettledRewardFee", monthSettleEarning.getIndirectSettledRewardFee());
            model.put(keyPrefix + "CarrierSettledRewardFee", monthSettleEarning.getCarrierSettledRewardFee());
            model.put(keyPrefix + "ChiefSettledRewardFee", monthSettleEarning.getChiefSettledRewardFee());
            model.put(keyPrefix + "CityAgentSettledRewardFee", monthSettleEarning.getCityAgentSettledRewardFee());
            model.put(keyPrefix + "DistrictAgentSettledRewardFee", monthSettleEarning.getDistrictAgentSettledRewardFee());
            model.put(keyPrefix + "RelationAgentSettledRewardFee", monthSettleEarning.getRelationAgentSettledRewardFee());
        }
        List<AllotTypeVo> list = new ArrayList<>();
        for (CommissionAllotType allotType : CommissionAllotType.values()) {
            if (allotType == CommissionAllotType.SELF_BUY && userService.isUserLevel(userId, UserLevel.PLUS)) {
                continue;
            }
            if (allotType == CommissionAllotType.CITY_AGENT && !agentService.isAgent(userId, AgentType.CITY)) {
                continue;
            }
            if (allotType == CommissionAllotType.DISTRICT_AGENT && !agentService.isAgent(userId, AgentType.DISTRICT)) {
                continue;
            }
            if (allotType == CommissionAllotType.RELATION_AGENT && !agentService.isAgent(userId, AgentType.RELATION)) {
                continue;
            }
            if (allotType == CommissionAllotType.CARRIER && !userService.isUserLevel(userId, UserLevel.CARRIER)) {
                continue;
            }
            AllotTypeVo vo = new AllotTypeVo();
            vo.setName(allotType.name());
            vo.setTitle(allotType.getTitle());
            vo.setCapitalizeName(StringUtils.capitalize(allotType.name().toLowerCase()));
            list.add(vo);
        }
        model.put("allotTypeList", list);
        return BusinessResponse.ok(model);
    }

    private void stat(Map<String, Object> model, UserCommissionEarningMapper.UserEstimateStatParam param) throws ParseException {
        Date now = new Date();
        List<UserCommissionEarning> lastEarningStat = userCommissionEarningMapper.userCommissionEarning(param);
        for (UserCommissionEarning userCommissionEarning : lastEarningStat) {
            String keyPrefix = null;
            if (param.getTimeDimension() == UserCommissionEarningMapper.TimeDimension.DAY) {
                Date date = DateUtils.parseDate(userCommissionEarning.getDate(), "yyyy-MM-dd");
                if (DateUtils.isSameDay(date, now)) {
                    //如果是当天，就是today
                    keyPrefix = "today";
                } else {
                    keyPrefix = "yesterday";
                }
            } else {
                Date date = DateUtils.parseDate(userCommissionEarning.getDate() + "-01", "yyyy-MM-dd");
                if (DateUtils.truncate(date, Calendar.MONTH).equals(DateUtils.truncate(now, Calendar.MONTH))) {
                    //如果是当天，就是today
                    keyPrefix = "month";
                } else {
                    keyPrefix = "lastMonth";
                }
            }
            model.put(keyPrefix + "EstimateCommissionFee", userCommissionEarning.getEstimateCommissionFee());
            model.put(keyPrefix + "EstimateRewardFee", userCommissionEarning.getEstimateRewardFee());
            model.put(keyPrefix + "OrderNum", userCommissionEarning.getOrderNum());
            model.put(keyPrefix + "SelfBuyEstimateOrderNum", userCommissionEarning.getSelfBuyOrderNum());
            model.put(keyPrefix + "DirectEstimateOrderNum", userCommissionEarning.getDirectOrderNum());
            model.put(keyPrefix + "IndirectEstimateOrderNum", userCommissionEarning.getIndirectOrderNum());
            model.put(keyPrefix + "CarrierEstimateOrderNum", userCommissionEarning.getCarrierOrderNum());
            model.put(keyPrefix + "ChiefEstimateOrderNum", userCommissionEarning.getChiefOrderNum());
            model.put(keyPrefix + "CityAgentEstimateOrderNum", userCommissionEarning.getCityAgentOrderNum());
            model.put(keyPrefix + "DistrictAgentEstimateOrderNum", userCommissionEarning.getDistrictAgentOrderNum());
            model.put(keyPrefix + "RelationAgentEstimateOrderNum", userCommissionEarning.getRelationAgentOrderNum());
            model.put(keyPrefix + "SelfBuyEstimateCommissionFee", userCommissionEarning.getSelfBuyEstimateCommissionFee());
            model.put(keyPrefix + "DirectEstimateCommissionFee", userCommissionEarning.getDirectEstimateCommissionFee());
            model.put(keyPrefix + "IndirectEstimateCommissionFee", userCommissionEarning.getIndirectEstimateCommissionFee());
            model.put(keyPrefix + "CarrierEstimateCommissionFee", userCommissionEarning.getCarrierEstimateCommissionFee());
            model.put(keyPrefix + "ChiefEstimateCommissionFee", userCommissionEarning.getChiefEstimateCommissionFee());
            model.put(keyPrefix + "CityAgentEstimateCommissionFee", userCommissionEarning.getCityAgentEstimateCommissionFee());
            model.put(keyPrefix + "DistrictAgentEstimateCommissionFee", userCommissionEarning.getDistrictAgentEstimateCommissionFee());
            model.put(keyPrefix + "RelationAgentEstimateCommissionFee", userCommissionEarning.getRelationAgentEstimateCommissionFee());
            model.put(keyPrefix + "SelfBuyEstimateRewardFee", userCommissionEarning.getSelfBuyEstimateRewardFee());
            model.put(keyPrefix + "DirectEstimateRewardFee", userCommissionEarning.getDirectEstimateRewardFee());
            model.put(keyPrefix + "IndirectEstimateRewardFee", userCommissionEarning.getIndirectEstimateRewardFee());
            model.put(keyPrefix + "CarrierEstimateRewardFee", userCommissionEarning.getCarrierEstimateRewardFee());
            model.put(keyPrefix + "ChiefEstimateRewardFee", userCommissionEarning.getChiefEstimateRewardFee());
            model.put(keyPrefix + "CityAgentEstimateRewardFee", userCommissionEarning.getCityAgentEstimateRewardFee());
            model.put(keyPrefix + "DistrictAgentEstimateRewardFee", userCommissionEarning.getDistrictAgentEstimateRewardFee());
            model.put(keyPrefix + "RelationAgentEstimateRewardFee", userCommissionEarning.getRelationAgentEstimateRewardFee());
        }
    }

    public static class AllotTypeVo {
        private String name;
        private String capitalizeName;

        private String title;

        public String getName() {
            return name;
        }

        public void setName(String name) {
            this.name = name;
        }

        public String getCapitalizeName() {
            return capitalizeName;
        }

        public void setCapitalizeName(String capitalizeName) {
            this.capitalizeName = capitalizeName;
        }

        public String getTitle() {
            return title;
        }

        public void setTitle(String title) {
            this.title = title;
        }
    }

}
